package com.ilop.sthome.mvp.present.scene;

import android.content.Context;
import android.content.Intent;

import com.example.common.base.OnCallBackToRefresh;
import com.example.common.mvp.BasePresenterImpl;
import com.ilop.sthome.common.CommonId;
import com.ilop.sthome.common.command.SendAutoCommand;
import com.ilop.sthome.data.enums.SmartDevice;
import com.ilop.sthome.data.greenDao.AutomationBean;
import com.ilop.sthome.data.greenDao.DefaultBean;
import com.ilop.sthome.data.greenDao.DeviceInfoBean;
import com.ilop.sthome.data.greenDao.SceneBean;
import com.ilop.sthome.mvp.contract.scene.DefaultContract;
import com.ilop.sthome.ui.activity.detail.common.ChooseMappingActivity;
import com.ilop.sthome.ui.activity.scene.ChooseActionActivity;
import com.ilop.sthome.ui.activity.scene.InputDetailActivity;
import com.ilop.sthome.ui.activity.scene.SettingActionActivity;
import com.ilop.sthome.ui.activity.scene.SettingHumitureActivity;
import com.ilop.sthome.ui.activity.scene.SettingTempControlActivity;
import com.ilop.sthome.ui.dialog.BaseDialog;
import com.ilop.sthome.utils.CoderUtils;
import com.ilop.sthome.utils.ConfigureUtil;
import com.ilop.sthome.utils.greenDao.utils.AutomationDaoUtil;
import com.ilop.sthome.utils.greenDao.utils.DefaultDaoUtil;
import com.ilop.sthome.utils.greenDao.utils.DeviceDaoUtil;
import com.ilop.sthome.utils.greenDao.utils.SceneDaoUtil;
import com.ilop.sthome.utils.tools.ByteUtil;
import com.siterwell.familywellplus.R;

import org.apache.commons.lang3.StringUtils;

import java.util.ArrayList;
import java.util.List;

/**
 * @author skygge
 * @date 2020-03-16.
 * GitHub：javofxu@github.com
 * email：skygge@yeah.net
 * description：
 */
public class DefaultPresenter extends BasePresenterImpl<DefaultContract.IView> implements DefaultContract.IPresent {

    private Context mContext;
    private String mDeviceName;
    private int mDeviceId;
    private int mPosition;
    private DefaultBean mDefault;
    private AutomationBean mAutomation;

    private List<DeviceInfoBean> mInputList;
    private List<DeviceInfoBean> mOutputList;

    private String mMapping;
    private String finalCRC;
    private String mAutoCode;

    public DefaultPresenter(Context mContext) {
        this.mContext = mContext;
    }

    @Override
    public void getDefaultData(long id) {
        mDefault = DefaultDaoUtil.getInstance().getDefaultDao().queryById(id);
        this.mDeviceName = mDefault.getDeviceName();
        this.mDeviceId = Integer.parseInt(mDefault.getDeviceId(), 16);
        List<AutomationBean> automationList = AutomationDaoUtil.getInstance().findAutomationByInType(mDefault.getRecommendId(), mDeviceName, mDeviceId);
        if (automationList.size()>0){
            mAutomation = automationList.get(0);
        }else {
            mAutomation = null;
        }
        mView.showTitle(mContext.getString(ConfigureUtil.getCommonName(mDefault.getRecommendId())));
        mView.showEditable(mDefault.getModify());
    }

    @Override
    public void getInputDevice() {
        if (mAutomation == null) {
            mInputList = new ArrayList<>();
            DeviceInfoBean device = new DeviceInfoBean();
            device.setDeviceName(mDeviceName);
            device.setDevice_ID(mDeviceId);
            device.setDevice_type(mDefault.getDeviceType());
            device.setDevice_status(mDefault.getInputCode());
            mInputList.add(device);
        }else {
            mInputList = mAutomation.getInputList();
        }
        mView.showInputList(mInputList);
    }

    @Override
    public void getOutputDevice() {
        if (mAutomation == null) {
            mOutputList = DefaultDaoUtil.getInstance().getDefaultOutputList(mDefault);
        }else {
            mOutputList = mAutomation.getOutputList();
        }
        mView.showOutputList(mOutputList);
    }

    @Override
    public void setInputList(List<DeviceInfoBean> deviceList) {
        mInputList = deviceList;
        mView.showInputList(deviceList);
    }

    @Override
    public void setOutputList(List<DeviceInfoBean> deviceList) {
        mOutputList = deviceList;
        mView.showOutputList(deviceList);
    }

    @Override
    public void addNewInput() {
        Intent addItem = new Intent(mContext, ChooseActionActivity.class);
        addItem.putExtra(CommonId.KEY_INPUT, true);
        addItem.putExtra(CommonId.KEY_LINKAGE, true);
        addItem.putExtra(CommonId.KEY_DEVICE_NAME, mDeviceName);
        mView.startActivityByIntent(addItem);
    }

    @Override
    public void addNewOutput() {
        Intent addItem = new Intent(mContext, ChooseActionActivity.class);
        addItem.putExtra(CommonId.KEY_INPUT, false);
        addItem.putExtra(CommonId.KEY_DEVICE_NAME, mDeviceName);
        mView.startActivityByIntent(addItem);
    }

    @Override
    public void saveAction() {
        if (mInputList.size() == 0){
            mView.showMsg(mContext.getString(R.string.intput_must_has_eq));
        }else if (mOutputList.size() == 0){
            mView.showMsg(mContext.getString(R.string.output_must_has_eq));
        }else {
            DeviceInfoBean mDeviceInfoBean = DeviceDaoUtil.getInstance().findGatewayByDeviceName(mDeviceName);
            SendAutoCommand mSendSceneData = new SendAutoCommand(mContext, mDeviceInfoBean);
            String finalCode = CoderUtils.getNewCode(mMapping, mDefault.getRecommendId(), mInputList, mOutputList);
            finalCRC = ByteUtil.stringToCRC(finalCode);
            if (mAutomation == null){
                mAutoCode = "FFFF" + finalCode + finalCRC;
                mSendSceneData.increaseAutomation(mAutoCode.toUpperCase());
            }else {
                String autoId = CoderUtils.setCodeSupplement2Byte(Integer.toHexString(mAutomation.getMid()));
                mAutoCode = autoId + finalCode + finalCRC;
                mSendSceneData.updateAutomation(mAutoCode.toUpperCase());
            }
            mView.showProgress();
        }
    }

    @Override
    public void updateAction(boolean isInput, int position) {
        this.mPosition = position;
        DeviceInfoBean device;
        if (isInput){
            device = mInputList.get(position);
        }else {
            device = mOutputList.get(position);
        }

        if ("PHONE".equals(device.getDevice_type())){
            Intent intent = new Intent(mContext, InputDetailActivity.class);
            intent.putExtra(CommonId.KEY_DEVICE_TYPE, "PHONE");
            mView.startActivityByIntent(intent);
        }else {
            Intent intent = new Intent();
            intent.putExtra(CommonId.KEY_INPUT, isInput);
            intent.putExtra(CommonId.KEY_UPDATE, true);
            intent.putExtra(CommonId.KEY_DEVICE, device);
            SmartDevice smartDevice = SmartDevice.getType(device.getDevice_type());
            switch (smartDevice){
                case EE_DEV_TH_CHECK:
                    intent.putExtra(CommonId.KEY_DEVICE_TYPE, mDefault.getRecommendId());//0D为温度/0E是湿度
                    intent.putExtra(CommonId.KEY_MESSAGE, device == mInputList.get(0));
                    intent.setClass(mContext, SettingHumitureActivity.class);
                    mView.startActivityByIntent(intent);
                    break;
                case EE_TEMP_CONTROL:
                    intent.setClass(mContext, SettingTempControlActivity.class);
                    mView.startActivityByIntent(intent);
                    break;
                default:
                    if ("12".equals(mDefault.getRecommendId())){
                        intent.putExtra(CommonId.KEY_MESSAGE, true);
                    }
                    intent.setClass(mContext, SettingActionActivity.class);
                    mView.startActivityByIntent(intent);
                    break;
            }
        }
    }

    @Override
    public void deleteAction(boolean isInput) {
        if (isInput){
            mInputList.remove(mPosition);
            setInputList(mInputList);
        }else {
            mOutputList.remove(mPosition);
            setOutputList(mOutputList);
        }
    }

    @Override
    public void onSaveSuccess(String id) {
        boolean isModify = true;
        if(mAutomation == null){
            isModify = false;
            int mAutoId = Integer.parseInt(id, 16);
            mAutomation = new AutomationBean();
            mAutomation.setMid(mAutoId);
            mAutomation.setAutomationOnly(mDeviceName + "-" + mAutoId);
            mAutomation.setDeviceName(mDeviceName);
        }
        mAutomation.setCode(mAutoCode);
        mAutomation.setCrcCord(finalCRC);
        mAutomation.setSceneId(mMapping);
        mAutomation.setReserve(mDefault.getRecommendId());
        mAutomation.setInputList(mInputList);
        mAutomation.setOutputList(mOutputList);
        if (isModify){
            AutomationDaoUtil.getInstance().getAutomationDao().update(mAutomation);
        }else {
            AutomationDaoUtil.getInstance().getAutomationDao().insert(mAutomation);
        }
        mView.finishActivity();
    }

    @Override
    public boolean checkInput(DeviceInfoBean device) {
        if (mInputList.size()>0) {
            for (DeviceInfoBean input : mInputList) {
                if (input.getDevice_type().equals(device.getDevice_type()) &&
                        input.getDevice_status().equals(device.getDevice_status())) {
                    return false;
                }
            }
        }
        return true;
    }

    @Override
    public boolean checkOutput(DeviceInfoBean device) {
        for (int i = 0; i < mOutputList.size(); i++) {
            if ("PHONE".equals(device.getDevice_type())){
                if ("PHONE".equals(mOutputList.get(i).getDevice_type())){
                    return false;
                }
            }
        }
        return true;
    }

    @Override
    public void checkUpdateInput(DeviceInfoBean device) {
        mInputList.set(mPosition, device);
        setInputList(mInputList);
    }

    @Override
    public void checkUpdateOutput(DeviceInfoBean device) {
        mOutputList.set(mPosition, device);
        setOutputList(mOutputList);
    }

    @Override
    public void chooseMapping() {
        Intent intent = new Intent(mContext, ChooseMappingActivity.class);
        intent.putExtra(CommonId.KEY_DEVICE_NAME, mDeviceName);
        intent.putExtra(CommonId.KEY_SCENE_ID, mMapping);
        mView.startActivityByIntent(intent);
    }

    @Override
    public void getMappingScene() {
        if (mAutomation == null){
            mMapping = mDefault.getMapping();
            switch (mMapping){
                case "0001":
                    mView.showMapping(mContext.getString(R.string.home_mode));
                    break;
                case "0002":
                    mView.showMapping(mContext.getString(R.string.out_mode));
                    break;
                case "0004":
                    mView.showMapping(mContext.getString(R.string.sleep_mode));
                    break;
                case "0FFF":
                    mView.showMapping(mContext.getString(R.string.all_scene));
                    break;
            }
        }else {
            mMapping = mAutomation.getSceneId();
            List<String> mapping = CoderUtils.getSceneList(mMapping);
            getMappingScene(mapping, false);
        }
    }

    @Override
    public void getMappingScene(List<String> mapping, boolean newCode) {
        List<SceneBean> mList = SceneDaoUtil.getInstance().findAllScene(mDeviceName);
        int mappingSize = mapping.size();
        if (mappingSize == mList.size()){
            mView.showMapping(mContext.getString(R.string.all_scene));
        }else {
            List<String> mapScene = new ArrayList<>();
            for (int i = 0; i < mappingSize; i++) {
                int sid = Integer.parseInt(mapping.get(i));
                for (SceneBean scene: mList) {
                    if (sid == scene.getSid()){
                        mapScene.add(getSceneName(sid, scene));
                    }
                }
            }
            String name;
            if (mapScene.size()>2){
                name = mapScene.get(0)+","+mapScene.get(1)+"...";
            }else {
                name = StringUtils.join(mapScene,",");
            }
            mView.showMapping(name);
        }
        if (newCode){
            mMapping = getSceneMapping(mapping);
        }
    }

    @Override
    public void whetherToSave(boolean hasModify) {
        if (hasModify){
            BaseDialog mDialog = new BaseDialog(mContext, new OnCallBackToRefresh() {
                @Override
                public void onConfirm() {
                    saveAction();
                }

                @Override
                public void onCancel() {
                    mView.finishActivity();
                }
            });
            mDialog.setMsg(mContext.getString(R.string.scene_has_modify));
            mDialog.show();
        }else {
            mView.finishActivity();
        }
    }

    private String getSceneName(int sid, SceneBean sceneBean){
        if (sid == 0){
            return mContext.getString(R.string.home_mode);
        }else if (sid == 1){
            return mContext.getString(R.string.out_mode);
        }else if (sid == 2){
            return mContext.getString(R.string.sleep_mode);
        }else {
            return sceneBean.getModleName();
        }
    }

    private String getSceneMapping(List<String> mapping){
        int sceneSize = mapping.size();
        if (sceneSize > 0) {
            StringBuilder index = new StringBuilder("000000000000");
            for (int i = 0; i < sceneSize; i++) {
                int position = Integer.parseInt(mapping.get(i));
                index.replace(position, position + 1, "1");
            }
            String fullCode = Integer.toHexString(Integer.parseInt(index.reverse().toString(), 2));
            return CoderUtils.setCodeSupplement2Byte(fullCode);
        }else {
            return null;
        }
    }
}
